#include "cmd_ls.h"
#include <grp.h>
#include <pwd.h>
#include <stdio.h>
#include <unistd.h>

int operate_ls(command_t *cmd){
	if(cmd->cmd_argc!=2)return -1;	
	strcpy(cmd->cmd_params[0],".");
	return cmd_list_directory(cmd->cmd_params[1]);
}
int cmd_list_directory(char* dirpath){
	DIR* dir=opendir(dirpath);
	if(NULL==dir)return -1;
	struct dirent* pdirent=NULL;
	file_attribute_t file;
	char path[SZ_PATH];
	int res=0;
	while((pdirent=readdir(dir))!=NULL){
		if(strcmp(pdirent->d_name,".")==0||strcmp(pdirent->d_name,"..")==0)continue;
		memset(&file,0,sizeof(file_attribute_t));
		strcpy(file.f_name,pdirent->d_name);
		make_path(path,dirpath);
		res=get_file_attr(&file,path,pdirent);
		if(res==-1) continue;
	}
	closedir(dir);
	return 1;

}
// 获取文件属性
int get_file_attr(file_attribute_t* file,char* path,struct dirent* pdirent){
	int ret=-1;
	// 判断是不是软链接
	if(pdirent->d_type==DT_LNK){
		ret=lstat(strcat(path,pdirent->d_name),&(file->f_stat));	
		ssize_t t=readlink(path,file->f_link_content,sizeof(file->f_link_content));	
	}else{
		ret=stat(strcat(path,pdirent->d_name),&(file->f_stat));
	}
	if(ret==-1)return -1;
	if(getchar_file_type(file)==-1)return -1;
	ret=get_file_permission(file);
	if(ret==-1) return -1;
	get_file_gname(file);
	get_file_uname(file);
	get_file_last_modify_time(file);
	show_file_attribute(file);	
	return 1;
}
void get_file_last_modify_time(file_attribute_t* file){
	char* t=ctime(&(file->f_stat.st_mtim.tv_sec));	
	t[strlen(t)-1]='\0';
	strcpy(file->f_mtime,t);
}

// 获取文件所属用户名及所属组名
void get_file_uname(file_attribute_t* file){
    struct passwd* p=getpwuid(file->f_stat.st_uid);
	strcpy(file->f_uname,p->pw_name);
}
void get_file_gname(file_attribute_t* file){
	struct group* g=getgrgid(file->f_stat.st_gid);
	strcpy(file->f_gname,g->gr_name);
}
// 获取文件权限
int get_file_permission(file_attribute_t* file){
	if(NULL==file)return -1;
	int index=8;
	char perm[]={'r','w','x'};
	mode_t mode=file->f_stat.st_mode;
	int i=0;
	for(;i<=8;i++){
		if((mode>>i)&1){
			file->f_permission[index]=perm[index%3];
		}else{
			file->f_permission[index]='-';
		}
		index--;
	}
	file->f_permission[i]='\0';
	return 1;
}

// 获取文件类型
int getchar_file_type(file_attribute_t* file){
	if(NULL==file)return -1;
	mode_t mode=file->f_stat.st_mode;
	char type=0;
	switch (mode & S_IFMT) {
         case S_IFBLK:  type='b';			break;
         case S_IFCHR:  type='c';			break;
         case S_IFDIR:	type='d';           break;
         case S_IFIFO:  type='i';           break;
         case S_IFLNK:  type='l';           break;
         case S_IFREG:  type='r';			break;
         case S_IFSOCK:	type='s';           break;
         default:							break;
	}
	file->f_type=type;
	return 1;	
}
void show_file_attribute(file_attribute_t* file){
	printf("%c\t%s\t%s\t%s\t%s\t",file->f_type,
									file->f_name,
									file->f_permission,
									file->f_uname,
									file->f_gname);
	printf("%ld\t%s\t====>%s\n",file->f_stat.st_size,file->f_mtime,file->f_link_content);
//	printf("Permissions: %o\n", (file->f_stat.st_mode) & (S_IRWXU | S_IRWXG | S_IRWXO));
}
void make_path(char* path,char* dest){
	strcpy(path,dest);
	strcat(path,"/");
}
